package utils

import (
	"crypto/rand"
	"crypto/sha256"
	"encoding/base64"
	"fmt"
)

// 生成一个随机的盐值，长度为size
func GenerateSalt(size int) (string, error) {
	salt := make([]byte, size)
	_, err := rand.Read(salt)
	if err != nil {
		return "", err
	}
	return base64.StdEncoding.EncodeToString(salt), nil
}

// 对密码进行哈希处理，使用给定的盐值并进行多次迭代
func HashPassword(password, salt string, iterations int) string {
	// 将密码和盐值组合成一个新的输入
	password1 := []byte(password)
	salt1, _ := base64.StdEncoding.DecodeString(salt)
	res, _ := Hash(password1, salt1, iterations)
	return base64.StdEncoding.EncodeToString(res)
}
func HashPassword2(password, salt string, iterations int) string {
	// 将密码和盐值组合成一个新的输入
	data := password + salt
	hash := sha256.New()

	// 进行迭代计算
	for i := 0; i < iterations; i++ {
		hash.Reset()
		hash.Write([]byte(data))
		data = fmt.Sprintf("%x", hash.Sum(nil)) // 将结果转为十六进制
	}

	return base64.StdEncoding.EncodeToString(hash.Sum(nil))
}
func Hash(bytes, salt []byte, hashIterations int) ([]byte, error) {
	// Create a new SHA256 hash instance
	hash := sha256.New()

	// If salt is provided, update the hash with the salt
	if len(salt) != 0 {
		hash.Write(salt)
	}

	// Update the hash with the input bytes
	hash.Write(bytes)

	// Perform the initial hash
	hashed := hash.Sum(nil)

	// Perform additional hash iterations
	for i := 0; i < hashIterations-1; i++ {
		hash.Reset()
		hash.Write(hashed)
		hashed = hash.Sum(nil)
	}

	return hashed, nil
}

// 第一个方法：使用随机盐值和密码进行加密
func Password(password string) (string, string, error) {
	salt, err := GenerateSalt(32) // 生成32字节的盐值
	if err != nil {
		return "", "", err
	}
	hashedPassword := HashPassword(password, salt, 2048)
	return hashedPassword, salt, nil
}

func Sha256(password string) string {
	hash := sha256.New()
	data := []byte(password)
	hash.Write(data)
	return base64.StdEncoding.EncodeToString(hash.Sum(nil))
}

// 第二个方法：使用提供的盐值和密码进行加密
func passwordBySalt(password, salt string) (string, string) {
	hashedPassword := HashPassword(password, salt, 2048)
	return hashedPassword, salt
}
